package category

import (
	"cgs-server/helper"
	"cgs-server/server"
	"cgs-server/server/assets/cgs_portal"
	"cgs-server/server/base"
	"cgs-server/server/model"
	"go.mongodb.org/mongo-driver/bson"
	"go.mongodb.org/mongo-driver/bson/primitive"
	"io/ioutil"
	"net/http"
	"strconv"
	"strings"
)

func init() {
	server.Post("/api/Cgs/Portal/Category/Add", Add, "添加应用分类", server.ConfigCategory)
	server.Get("/api/Cgs/Portal/Category/List", List, "获取应用分类", server.Login)
	server.Get("/api/Cgs/Portal/Category/ListPage", ListPage, "分页获取应用分类", server.Login)
	server.Get("/api/Cgs/Portal/Category/Detail", Detail, "获取应用分类详情", server.Login)
	server.Post("/api/Cgs/Portal/Category/Edit", Edit, "更新应用分类", server.ConfigCategory)
	server.Post("/api/Cgs/Portal/Category/Delete", Delete, "删除应用分类", server.ConfigCategory)

}

// Add add a category
func Add(w http.ResponseWriter, r *http.Request) {
	r.Body = http.MaxBytesReader(w, r.Body, int64(100<<20))
	s, _ := ioutil.ReadAll(r.Body) //把  body 内容读入字符串 s
	category := &Category{}
	err := helper.FromJSON(s, category)
	if err != nil {
		_, _ = helper.WriteJSON(w, server.Fail(err.Error()))
		return
	}
	//	校验
	err = helper.GetValidator().Struct(category)
	if err != nil {
		_, _ = helper.WriteJSON(w, server.Fail(err.Error()))
		return
	}
	if _, ok := cgs_portal.VisualTypes[category.VisualType]; !ok {
		_, _ = helper.WriteJSON(w, server.Fail("VisualType is not existed."))
		return
	}

	duModel := base.GenerateDataUserModel(category, r)
	categoryService := NewCategoryService()
	err = categoryService.Save(duModel)
	if err != nil {
		_, _ = helper.WriteJSON(w, server.Fail(err.Error()))
		return
	}
	_, _ = helper.WriteJSON(w, server.OK("Add successfully!").WithData(bson.M{
		"id": category.GetId(),
	}))
}

func List(w http.ResponseWriter, r *http.Request) {
	// 根据VisualType 过滤
	_ = r.ParseForm()
	visualType := strings.TrimSpace(r.FormValue("VisualType"))
	if visualType == "" {
		_, _ = helper.WriteJSON(w, server.Fail("VisualType is not allowed empty!"))
		return
	}
	if _, ok := cgs_portal.VisualTypes[visualType]; !ok {
		_, _ = helper.WriteJSON(w, server.Fail("VisualType is not existed."))
		return
	}

	user, err := base.GetCurrentUser(r)
	categoryService := NewCategoryService()
	res, err := categoryService.ListAll(visualType, user)

	if err != nil {
		_, _ = helper.WriteJSON(w, server.Fail(err.Error()))
		return
	}

	if res == nil {
		res = []*Vo{}
	}

	_, _ = helper.WriteJSON(w, server.OK("Get Successfully!").WithData(res))
}

func ListPage(w http.ResponseWriter, r *http.Request) {
	// 根据VisualType 过滤
	_ = r.ParseForm()
	visualType := strings.TrimSpace(r.FormValue("VisualType"))
	if visualType == "" {
		_, _ = helper.WriteJSON(w, server.Fail("VisualType is not allowed empty!"))
		return
	}
	if _, ok := cgs_portal.VisualTypes[visualType]; !ok {
		_, _ = helper.WriteJSON(w, server.Fail("VisualType is not existed."))
		return
	}

	current, err := strconv.ParseInt(r.FormValue("current"), 10, 64)
	if err != nil {
		_, _ = helper.WriteJSON(w, server.Fail(err.Error()))
		return
	}
	size, err := strconv.ParseInt(r.FormValue("size"), 10, 64)
	if err != nil {
		_, _ = helper.WriteJSON(w, server.Fail(err.Error()))
		return
	}

	duModel := base.GenerateDataUserModel(&Category{VisualType: visualType}, r)
	duModel.Page = &model.Page{
		Current: current,
		Size:    size,
	}

	categoryService := NewCategoryService()
	res, err := categoryService.ListPage(duModel)

	if err != nil {
		_, _ = helper.WriteJSON(w, server.Fail(err.Error()))
		return
	}

	_, _ = helper.WriteJSON(w, server.OK("Get Successfully!").WithData(res))
}

func Detail(w http.ResponseWriter, r *http.Request) {
	// 需要id和类型
	visualType := strings.TrimSpace(r.FormValue("VisualType"))
	if visualType == "" {
		_, _ = helper.WriteJSON(w, server.Fail("VisualType is not allowed empty!"))
		return
	}
	if _, ok := cgs_portal.VisualTypes[visualType]; !ok {
		_, _ = helper.WriteJSON(w, server.Fail("VisualType is not existed."))
		return
	}

	// id
	id, err := primitive.ObjectIDFromHex(strings.TrimSpace(r.FormValue("ID")))
	if err != nil {
		id, err = primitive.ObjectIDFromHex(strings.TrimSpace(r.FormValue("id")))
	}
	if err != nil {
		_, _ = helper.WriteJSON(w, server.Fail("ID is not allowed to be empty."))
		return
	}

	duModel := base.GenerateDataUserModel(&Category{
		ID:         id,
		VisualType: visualType,
	}, r)

	categoryService := NewCategoryService()
	res, err := categoryService.GetOne(duModel)
	if err != nil {
		helper.WriteJSON(w, server.Fail(err.Error()))
		return
	}
	helper.WriteJSON(w, server.OK("Get successfully.").WithData(res))
}

func Edit(w http.ResponseWriter, r *http.Request) {
	r.Body = http.MaxBytesReader(w, r.Body, int64(100<<20))
	s, _ := ioutil.ReadAll(r.Body) //把  body 内容读入字符串 s
	category := &Category{}
	err := helper.FromJSON(s, category)
	if err != nil {
		_, _ = helper.WriteJSON(w, server.Fail(err.Error()))
		return
	}
	//id, err := primitive.ObjectIDFromHex(strings.TrimSpace(category.ID))
	id := category.ID
	if id.IsZero() {
		_, _ = helper.WriteJSON(w, server.Fail("ID is not allowed to be empty."))
		return
	}
	if category.CategoryKey == "" {
		_, _ = helper.WriteJSON(w, server.Fail("name is not allowed to be empty."))
		return
	}
	if _, ok := cgs_portal.VisualTypes[category.VisualType]; !ok {
		_, _ = helper.WriteJSON(w, server.Fail("VisualType is not existed."))
		return
	}

	duModel := base.GenerateDataUserModel(category, r)
	categoryService := NewCategoryService()
	err = categoryService.Update(duModel)
	if err != nil {
		_, _ = helper.WriteJSON(w, server.Fail(err.Error()))
		return
	}
	_, _ = helper.WriteJSON(w, server.OK("Update successfully!"))
}

func Delete(w http.ResponseWriter, r *http.Request) {
	id, err := primitive.ObjectIDFromHex(strings.TrimSpace(r.FormValue("ID")))
	if err != nil {
		_, _ = helper.WriteJSON(w, server.Fail("ID is not allowed to be empty."))
		return
	}

	duModel := base.GenerateDataUserModel(&Category{
		ID: id,
	}, r)

	categoryService := NewCategoryService()
	err = categoryService.Remove(duModel)
	if err != nil {
		_, _ = helper.WriteJSON(w, server.Fail(err.Error()))
		return
	}
	_, _ = helper.WriteJSON(w, server.OK("Delete successfully!"))
}
